package autoz.core;

import java.io.File;
import java.util.List;

import org.eclipse.epsilon.egl.EglFileGeneratingTemplate;
import org.eclipse.epsilon.egl.EglFileGeneratingTemplateFactory;
import org.eclipse.epsilon.egl.EglTemplate;
import org.eclipse.epsilon.egl.EglTemplateFactory;
import org.eclipse.epsilon.egl.exceptions.EglRuntimeException;
import org.eclipse.epsilon.egl.execute.context.IEglContext;
import org.eclipse.epsilon.eol.exceptions.EolRuntimeException;
import org.eclipse.epsilon.eol.execute.context.IEolContext;
import org.eclipse.epsilon.eol.models.IModel;
import org.eclipse.epsilon.eol.types.IToolNativeTypeDelegate;

import autoz.core.tools.AliasTool;

public class AutozEngine {
	
	List<IModel> models;
	String templateLogicFileLocation;
	
	public AutozEngine(List<IModel> models, String templateLogicFileLocation){
		this.models = models;
		this.templateLogicFileLocation = templateLogicFileLocation;
	}
	
	/**
	 * Execute the specified template logic and returns the generated Z.
	 * @return A string containing a latex-Z representation of the diagrams
	 * @throws Exception
	 */
	public String generateToString() throws EglRuntimeException {
		String spec = "";
		
		EglTemplateFactory eglTemplateFactory = new EglTemplateFactory();
		IEglContext context = eglTemplateFactory.getContext();
		
		for (IModel m : models){
			context.getModelRepository().addModel(m);	
		}
		
		EglTemplate template = eglTemplateFactory.load(templateLogicFileLocation);
		spec = template.process();
		
		return spec;
	}
	/**
	 * Execute the specified template logic and saves the generated Z to the
	 * specified file.
	 * @param file The file where the Z should be saved.
	 * @throws Exception
	 */
	public void generateToFile(File file) throws EglRuntimeException {
		EglFileGeneratingTemplateFactory eglTemplateFactory = new EglFileGeneratingTemplateFactory();
		IEglContext context = eglTemplateFactory.getContext();
		
		// Register the alias tool
		context.getNativeTypeDelegates().add(new IToolNativeTypeDelegate() {
			
			@Override
			public boolean knowsAbout(String arg0) {
				if ("autoz.core.tools.AliasTool".equals(arg0))
					return true;
				
				return false;
			}
			
			@Override
			public Object createInstance(String arg0, List<Object> arg1,
					IEolContext context) throws EolRuntimeException {
				return new AliasTool(context);
			}
		});
		
		for (IModel m : models){
			context.getModelRepository().addModel(m);	
		}
		
		EglTemplate template = eglTemplateFactory.load(templateLogicFileLocation);
		((EglFileGeneratingTemplate)template).generate(file.getAbsolutePath());
	}
}
